﻿using System;
using System.Linq;
using Biz.Buffer;
using Biz.EF.Platform.Kq;

using Hjt212Parser;
using log4net;

namespace Biz.Process
{
    public static class ProcessorData
    {
        private static ILog log = LogManager.GetLogger(typeof(ProcessorData));
        /// <summary>
        /// 实时数据2011指令处理
        /// </summary>
        /// <param name="pCtx"></param>
        /// <param name="content"></param>
        public static void Process2011(PlatformYgContext pCtx, string content)
        {
            try
            {
                var lastTotalNum = Process_Envi_PS_Waste_Water_Flow(pCtx, content);
                var mn = Parser.GetStringByKey("MN", content);
                if (string.IsNullOrEmpty(mn)) return;
                var datatime = Parser.GetDateTimeByKey("DataTime", content);
                if (!datatime.HasValue) return;
                var letport = CommonInformation.GetLetportByMn(mn);
                if (letport == null) return;

                var cou = Parser.GetDecimalByKey("B01-Cou", content) ?? 0;
                var instantFlow = Parser.GetDecimalByKey("B01-Rtd", content) ?? 0;
                var begin = new DateTime(datatime.Value.Year, datatime.Value.Month, datatime.Value.Day, datatime.Value.Hour, 0,
                    0);
                var end = begin.AddHours(1).AddSeconds(-1);
                var hour = pCtx.Envi_PS_Waste_Water_Flow_Hour_Data
                    .Where(t => t.Date_Time >= begin)
                    .Where(t => t.Date_Time <= end)
                    .Where(t => t.Pollution_Source_ID.Equals(letport.Pollution_Source_Id + ""))
                    .FirstOrDefault(t => t.Let_Port_ID.Equals(letport.ID + ""));
                if (hour == null)
                {
                    hour = new Envi_PS_Waste_Water_Flow_Hour_Data
                    {
                        Pollution_Source_ID = letport.Pollution_Source_Id + "",
                        Let_Port_ID = letport.ID + "",
                        Date_Time = begin,
                        Flow = cou,
                        Time_Flow = instantFlow,
                        COD_Time_Measure = Parser.GetDecimalByKey("011-Rtd", content) ?? 0
                        //AN_Time_Measure = Parser.GetDecimalByKey("060-Rtd", content) ?? -1
                    };
                    pCtx.Envi_PS_Waste_Water_Flow_Hour_Data.Add(hour);
                    pCtx.SaveChanges();
                }
                else
                {
                    hour.Date_Time = begin;
                    hour.Flow += cou;
                    hour.Time_Flow = instantFlow;
                    hour.COD_Time_Measure = Parser.GetDecimalByKey("011-Rtd", content) ?? 0;
                    //hour.AN_Time_Measure = Parser.GetDecimalByKey("060-Rtd", content) ?? -1;
                    pCtx.SaveChanges();
                }
                var hourCorrect = pCtx.Envi_PS_Waste_Water_Flow_Hour_Correct_Data
                    .Where(t => t.Date_Time >= begin)
                    .Where(t => t.Date_Time <= end)
                    .Where(t => t.Pollution_Source_ID.Equals(letport.Pollution_Source_Id + ""))
                    .FirstOrDefault(t => t.Let_Port_ID.Equals(letport.ID + ""));
                if (hourCorrect == null)
                {
                    hourCorrect = new Envi_PS_Waste_Water_Flow_Hour_Correct_Data
                    {
                        Pollution_Source_ID = letport.Pollution_Source_Id + "",
                        Let_Port_ID = letport.ID + "",
                        Date_Time = begin,
                        Flow = cou,
                        Time_Flow = instantFlow,
                        COD_Time_Measure = Parser.GetDecimalByKey("011-Rtd", content) ?? 0
                        //AN_Time_Measure = Parser.GetDecimalByKey("060-Rtd", content) ?? -1
                    };
                    pCtx.Envi_PS_Waste_Water_Flow_Hour_Correct_Data.Add(hourCorrect);
                    pCtx.SaveChanges();
                }
                else
                {
                    //hourCorrect.Pollution_Source_ID = letport.Pollution_Source_Id + "";
                    //hourCorrect.Let_Port_ID = letport.ID + "";
                    hourCorrect.Date_Time = begin;
                    hourCorrect.Flow += cou;
                    hourCorrect.Time_Flow = instantFlow;
                    hourCorrect.COD_Time_Measure = Parser.GetDecimalByKey("011-Rtd", content) ?? 0;
                    //hourCorrect.AN_Time_Measure = Parser.GetDecimalByKey("060-Rtd", content) ?? -1;
                    pCtx.SaveChanges();
                }
            }
            catch (Exception ex)
            {
                log.Error(ex);
            }
        }
        private static decimal? Process_Envi_PS_Waste_Water_Flow(PlatformYgContext pCtx, string content)
        {
            decimal? lastTotalNum = 0;
            try
            {

                var mn = Parser.GetStringByKey("MN", content);
                if (string.IsNullOrEmpty(mn)) return null;
                var datatime = Parser.GetDateTimeByKey("DataTime", content);
                if (!datatime.HasValue) return null;
                var letport = CommonInformation.GetLetportByMn(mn);
                if (letport == null) return null;
                var licence =
                    CommonInformation.GetAllLicencess()
                        .FirstOrDefault(t => t.Pollution_Source_ID == letport.Pollution_Source_Id);
                //总量控制器上行是Cou
                //接县排是TotalFlow
                var cou = Parser.GetDecimalByKey("B01-Cou", content) ?? 0;
                var rtd = Parser.GetDecimalByKey("B01-Rtd", content) ?? 0;
                var theLastItemInFlow =
                    pCtx.Envi_PS_Waste_Water_Flow.Where(t => t.Pollution_Source_ID == letport.Pollution_Source_Id)
                        .Where(t => t.Let_Port_ID == letport.ID)
                        .OrderByDescending(t => t.Monitor_Time).FirstOrDefault();
                var yearDays =
                       (DateTimeHelper.NextYear(datatime.Value) - DateTimeHelper.YearBegin(datatime.Value)).TotalDays;
                var quarterDays =
                    (DateTimeHelper.NextQuarter(datatime.Value) - DateTimeHelper.QuarterBegin(datatime.Value))
                        .TotalDays;
                var monthDays =
                    (DateTimeHelper.NextMonth(datatime.Value) - DateTimeHelper.MonthBegin(datatime.Value))
                        .TotalDays;
                var cod = Parser.GetDecimalByKey("011-Rtd", content);
                if (theLastItemInFlow == null)
                {
                    // ReSharper disable once UseObjectOrCollectionInitializer
                    theLastItemInFlow = new Envi_PS_Waste_Water_Flow();

                    //基本信息
                    theLastItemInFlow.Let_Port_ID = letport.ID;
                    theLastItemInFlow.Pollution_Source_ID = letport.Pollution_Source_Id;
                    theLastItemInFlow.Pollution_Source_Name = letport.Pollution_Source_Name;
                    theLastItemInFlow.OnLine = 0;

                    //污水流量、排放量，第一次累计流量初始化，当天、当月、当季、当年排放量均为流速*15分钟/60分钟
                    theLastItemInFlow.Instant_Flow = rtd;
                    theLastItemInFlow.Total_Flow = 0;
                    theLastItemInFlow.Today_Flow = 0;
                    theLastItemInFlow.Month_Flow = 0;
                    theLastItemInFlow.Quarter_Flow = 0;
                    theLastItemInFlow.Year_Flow = 0;
                    //初始化污水当天、当月、当季、当年允许量
                    theLastItemInFlow.Day_Audit_Flow = licence == null
                        ? (decimal)0.01
                        : (licence.Waster_Day_Let_Measure ?? (decimal)0.01);
                    theLastItemInFlow.Month_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                         Decimal.Parse(monthDays.ToString("F2"));
                    theLastItemInFlow.Quarter_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                           Decimal.Parse(quarterDays.ToString("F2"));
                    theLastItemInFlow.Year_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                        Decimal.Parse(yearDays.ToString("F2"));
                    //计算污水当天、当月、当季、当年剩余量
                    theLastItemInFlow.Day_Remain_Flow = theLastItemInFlow.Day_Audit_Flow - theLastItemInFlow.Today_Flow;
                    theLastItemInFlow.Month_Remain_Flow = theLastItemInFlow.Month_Audit_Flow -
                                                          theLastItemInFlow.Month_Flow;
                    theLastItemInFlow.Quarter_Remain_Flow = theLastItemInFlow.Quarter_Audit_Flow -
                                                            theLastItemInFlow.Quarter_Flow;
                    theLastItemInFlow.Year_Remain_Flow = theLastItemInFlow.Year_Audit_Flow - theLastItemInFlow.Year_Flow;
                    //计算污水当天、当月、当季、当年排放比
                    theLastItemInFlow.Year_Let_Per = theLastItemInFlow.Year_Flow * 100 / theLastItemInFlow.Year_Audit_Flow;
                    theLastItemInFlow.Quarter_Let_Per = theLastItemInFlow.Quarter_Flow * 100 /
                                                        theLastItemInFlow.Quarter_Audit_Flow;
                    theLastItemInFlow.Let_Per = theLastItemInFlow.Month_Flow * 100 / theLastItemInFlow.Month_Audit_Flow;
                    //初始化COD当天、当月、当季、当年允许量
                    theLastItemInFlow.COD_Year_Audit_Measure = licence == null
                        ? (decimal)0.01
                        : (licence.COD_Allow_Let_Measure ?? (decimal)0.01);
                    theLastItemInFlow.COD_Quarter_Audit_Measure = theLastItemInFlow.COD_Year_Audit_Measure /
                                                                  Decimal.Parse(yearDays.ToString("F2")) *
                                                                  Decimal.Parse(quarterDays.ToString("F2"));
                    theLastItemInFlow.COD_Month_Audit_Measure = theLastItemInFlow.COD_Year_Audit_Measure /
                                                                Decimal.Parse(yearDays.ToString("F2")) *
                                                                Decimal.Parse(monthDays.ToString("F2"));
                    //其实就是011的浓度avg
                    if (cod != null)
                    {
                        theLastItemInFlow.COD = cod;
                        //计算COD当天、当月、当季、当年排放量
                        theLastItemInFlow.COD_Month_Measure = 0;
                        theLastItemInFlow.COD_Quarter_Measure = 0;
                        theLastItemInFlow.COD_Year_Measure = 0;
                        //计算COD当天、当月、当季、当年剩余量
                        theLastItemInFlow.COD_Month_Remain_Measure = theLastItemInFlow.COD_Month_Audit_Measure -
                                                                     theLastItemInFlow.COD_Month_Measure;
                        theLastItemInFlow.COD_Quarter_Remain_Measure = theLastItemInFlow.COD_Quarter_Audit_Measure -
                                                                       theLastItemInFlow.COD_Quarter_Measure;
                        theLastItemInFlow.COD_Year_Remain_Measure = theLastItemInFlow.COD_Year_Audit_Measure -
                                                                    theLastItemInFlow.COD_Year_Measure;
                        //计算COD当天、当月、当季、当年排放比
                        theLastItemInFlow.COD_Let_Per = theLastItemInFlow.COD_Month_Measure * 100 /
                                                        theLastItemInFlow.COD_Month_Audit_Measure;
                        theLastItemInFlow.COD_Quarter_Let_Per = theLastItemInFlow.COD_Quarter_Measure * 100 /
                                                                theLastItemInFlow.COD_Quarter_Audit_Measure;
                        theLastItemInFlow.COD_Year_Let_Per = theLastItemInFlow.COD_Year_Measure * 100 /
                                                             theLastItemInFlow.COD_Year_Audit_Measure;
                    }
                    //污水监测时间
                    theLastItemInFlow.Monitor_Time = datatime;

                    pCtx.Envi_PS_Waste_Water_Flow.Add(theLastItemInFlow);
                    pCtx.SaveChanges();
                }
                lastTotalNum = theLastItemInFlow.Total_Flow;
                //theLastItemInFlow.Let_Port_ID = letport.ID;
                //theLastItemInFlow.Pollution_Source_ID = letport.Pollution_Source_Id;
                //theLastItemInFlow.Pollution_Source_Name = letport.Pollution_Source_Name;
                theLastItemInFlow.OnLine = 0;

                theLastItemInFlow.Instant_Flow = rtd;
                theLastItemInFlow.Total_Flow += cou;
                //TODO:接县排此处不同,要重新算下Cou
                //接收到的时间是否与最新一条时间是否同一天来计算日排放量、日允许量、日剩余量、日排放比
                if (theLastItemInFlow.Monitor_Time != null && theLastItemInFlow.Monitor_Time.Value.Day != datatime.Value.Day)
                {
                    theLastItemInFlow.Today_Flow = cou;
                }
                else
                {
                    theLastItemInFlow.Today_Flow += cou;
                }
                theLastItemInFlow.Day_Audit_Flow = licence == null
                    ? (decimal)0.01
                    : (licence.Waster_Day_Let_Measure ?? (decimal)0.01);
                theLastItemInFlow.Day_Remain_Flow = theLastItemInFlow.Day_Audit_Flow - theLastItemInFlow.Today_Flow;
                //接收到的时间是否与最新一条时间是否同一月来计算月排放量、月允许量、月剩余量、月排放比
                if (theLastItemInFlow.Monitor_Time != null && theLastItemInFlow.Monitor_Time.Value.Month != datatime.Value.Month)
                {
                    theLastItemInFlow.Month_Flow = cou;
                }
                else
                {
                    theLastItemInFlow.Month_Flow += cou;
                }
                theLastItemInFlow.Month_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                       Decimal.Parse(monthDays.ToString("F2"));
                theLastItemInFlow.Month_Remain_Flow = theLastItemInFlow.Month_Audit_Flow -
                                                     theLastItemInFlow.Month_Flow;
                theLastItemInFlow.Let_Per = theLastItemInFlow.Month_Flow * 100 / theLastItemInFlow.Month_Audit_Flow;
                //接收到的时间是否与最新一条时间是否同一季来计算季排放量、季允许量、季剩余量、季排放比
                if (theLastItemInFlow.Monitor_Time != null && DateTimeHelper.QuarterBegin(theLastItemInFlow.Monitor_Time.Value) != DateTimeHelper.QuarterBegin(datatime.Value))
                {
                    theLastItemInFlow.Quarter_Flow = cou;
                }
                else
                {
                    theLastItemInFlow.Quarter_Flow += cou;
                }

                theLastItemInFlow.Quarter_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                       Decimal.Parse(quarterDays.ToString("F2"));
                theLastItemInFlow.Quarter_Remain_Flow = theLastItemInFlow.Quarter_Audit_Flow -
                                                       theLastItemInFlow.Quarter_Flow;
                theLastItemInFlow.Quarter_Let_Per = theLastItemInFlow.Quarter_Flow * 100 /
                                                  theLastItemInFlow.Quarter_Audit_Flow;
                //接收到的时间是否与最新一条时间是否同一年来计算年排放量、年允许量、年剩余量、年排放比
                if (theLastItemInFlow.Monitor_Time != null && theLastItemInFlow.Monitor_Time.Value.Year != datatime.Value.Year)
                {
                    theLastItemInFlow.Year_Flow = cou;
                }
                else
                {
                    theLastItemInFlow.Year_Flow += cou;
                }
                theLastItemInFlow.Year_Audit_Flow = theLastItemInFlow.Day_Audit_Flow *
                                                    Decimal.Parse(yearDays.ToString("F2"));
                theLastItemInFlow.Year_Remain_Flow = theLastItemInFlow.Year_Audit_Flow - theLastItemInFlow.Year_Flow;
                theLastItemInFlow.Year_Let_Per = theLastItemInFlow.Year_Flow * 100 / theLastItemInFlow.Year_Audit_Flow;


                theLastItemInFlow.COD_Year_Audit_Measure = licence == null
                    ? (decimal)0.01
                    : (licence.COD_Allow_Let_Measure ?? (decimal)0.01);
                theLastItemInFlow.COD_Quarter_Audit_Measure = theLastItemInFlow.COD_Year_Audit_Measure /
                                                              Decimal.Parse(yearDays.ToString("F2")) *
                                                              Decimal.Parse(quarterDays.ToString("F2"));
                theLastItemInFlow.COD_Month_Audit_Measure = theLastItemInFlow.COD_Year_Audit_Measure /
                                                            Decimal.Parse(yearDays.ToString("F2")) *
                                                            Decimal.Parse(monthDays.ToString("F2"));
                //其实就是011的浓度avg
                if (cod != null)
                {
                    theLastItemInFlow.COD = cod ?? 0;
                    if (theLastItemInFlow.Monitor_Time != null && theLastItemInFlow.Monitor_Time.Value.Month != datatime.Value.Month)
                    {
                        theLastItemInFlow.COD_Month_Measure = theLastItemInFlow.COD * cou / 1000;
                    }
                    else
                    {
                        theLastItemInFlow.COD_Month_Measure += theLastItemInFlow.COD * cou / 1000;
                    }
                    if (theLastItemInFlow.Monitor_Time != null && DateTimeHelper.QuarterBegin(theLastItemInFlow.Monitor_Time.Value) != DateTimeHelper.QuarterBegin(datatime.Value))
                    {
                        theLastItemInFlow.COD_Quarter_Measure = theLastItemInFlow.COD * cou / 1000;
                    }
                    else
                    {
                        theLastItemInFlow.COD_Quarter_Measure += theLastItemInFlow.COD * cou / 1000;
                    }

                    if (theLastItemInFlow.Monitor_Time != null && theLastItemInFlow.Monitor_Time.Value.Year != datatime.Value.Year)
                    {
                        theLastItemInFlow.COD_Year_Measure = theLastItemInFlow.COD * cou / 1000;
                    }
                    else
                    {
                        theLastItemInFlow.COD_Year_Measure += theLastItemInFlow.COD * cou / 1000;
                    }
                    theLastItemInFlow.COD_Month_Remain_Measure = theLastItemInFlow.COD_Month_Audit_Measure -
                                                                 theLastItemInFlow.COD_Month_Measure;
                    theLastItemInFlow.COD_Quarter_Remain_Measure = theLastItemInFlow.COD_Quarter_Audit_Measure -
                                                                   theLastItemInFlow.COD_Quarter_Measure;
                    theLastItemInFlow.COD_Year_Remain_Measure = theLastItemInFlow.COD_Year_Audit_Measure -
                                                                theLastItemInFlow.COD_Year_Measure;
                    theLastItemInFlow.COD_Let_Per = theLastItemInFlow.COD_Month_Measure * 100 /
                                                    theLastItemInFlow.COD_Month_Audit_Measure;
                    theLastItemInFlow.COD_Quarter_Let_Per = theLastItemInFlow.COD_Quarter_Measure * 100 /
                                                            theLastItemInFlow.COD_Quarter_Audit_Measure;
                    theLastItemInFlow.COD_Year_Let_Per = theLastItemInFlow.COD_Year_Measure * 100 /
                                                         theLastItemInFlow.COD_Year_Audit_Measure;
                }
                theLastItemInFlow.Monitor_Time = datatime;
                pCtx.SaveChanges();
            }
            catch (Exception ex)
            {
                log.Error(ex);
            }
            return lastTotalNum;
        }
    }
}
